package com.windy.player.player;

import android.animation.Animator;
import android.animation.AnimatorListenerAdapter;
import android.animation.AnimatorSet;
import android.animation.ObjectAnimator;
import android.app.Activity;
import android.content.Context;
import android.content.pm.ActivityInfo;
import android.content.res.Configuration;
import android.media.AudioManager;
import android.os.Handler;
import android.os.Looper;
import android.os.Message;
import android.support.v7.app.ActionBar;
import android.support.v7.app.AppCompatActivity;
import android.util.DisplayMetrics;
import android.util.Log;
import android.view.GestureDetector;
import android.view.MotionEvent;
import android.view.OrientationEventListener;
import android.view.Surface;
import android.view.View;
import android.view.ViewGroup;
import android.view.WindowManager;
import android.view.animation.DecelerateInterpolator;
import android.widget.ImageView;
import android.widget.ProgressBar;
import android.widget.SeekBar;
import android.widget.TextView;

import com.windy.player.R;
import com.windy.player.utils.StringUtil;
import com.windy.player.widget.IRenderView;
import com.windy.player.widget.IjkVideoView;

import tv.danmaku.ijk.media.player.IMediaPlayer;
import tv.danmaku.ijk.media.player.IjkMediaPlayer;

/**
 * Created by tcking on 15/10/27.
 */
public class WindyPlayer {

    private final static String TAG = /*WindyPlayer.class.getSimpleName()*/"dingfeng";

    /**
     * fitParent:scale the video uniformly (maintain the video's aspect ratio) so that both dimensions (width and height) of the video will be equal to or **less** than the corresponding dimension of the view. like ImageView's `CENTER_INSIDE`.等比缩放,画面填满view。
     */
    public static final String SCALETYPE_FITPARENT = "fitParent";
    /**
     * fillParent:scale the video uniformly (maintain the video's aspect ratio) so that both dimensions (width and height) of the video will be equal to or **larger** than the corresponding dimension of the view .like ImageView's `CENTER_CROP`.等比缩放,直到画面宽高都等于或小于view的宽高。
     */
    public static final String SCALETYPE_FILLPARENT = "fillParent";
    /**
     * wrapContent:center the video in the view,if the video is less than view perform no scaling,if video is larger than view then scale the video uniformly so that both dimensions (width and height) of the video will be equal to or **less** than the corresponding dimension of the view. 将视频的内容完整居中显示，如果视频大于view,则按比例缩视频直到完全显示在view中。
     */
    public static final String SCALETYPE_WRAPCONTENT = "wrapContent";
    /**
     * fitXY:scale in X and Y independently, so that video matches view exactly.不剪裁,非等比例拉伸画面填满整个View
     */
    public static final String SCALETYPE_FITXY = "fitXY";
    /**
     * 16:9:scale x and y with aspect ratio 16:9 until both dimensions (width and height) of the video will be equal to or **less** than the corresponding dimension of the view.不剪裁,非等比例拉伸画面到16:9,并完全显示在View中。
     */
    public static final String SCALETYPE_16_9 = "16:9";
    /**
     * 4:3:scale x and y with aspect ratio 4:3 until both dimensions (width and height) of the video will be equal to or **less** than the corresponding dimension of the view.不剪裁,非等比例拉伸画面到4:3,并完全显示在View中。
     */
    public static final String SCALETYPE_4_3 = "4:3";

    // video status
    private int STATUS_ERROR = -1;
    private int STATUS_IDLE = 0;
    private int STATUS_LOADING = 1;
    private int STATUS_PLAYING = 2;
    private int STATUS_PAUSE = 3;
    private int STATUS_COMPLETED = 4;
    private int status = STATUS_IDLE;

    private String mUrl;
    private final Activity mActivity;
    private final AudioManager mAudioManager;
    private final GestureDetector mGestureDetector;
    private OrientationEventListener mOrientationEventListener;

    private final int initHeight;
    private int screenWidthPixels;
    private final int mMaxVolume;

    private final static String DEFAULT_SCALETYPE = SCALETYPE_FILLPARENT;
    private final static int DEFAULT_TIMEOUT = 3000;
    private final static int MAX_TIMEOUT = 3600000;
    private static long DEFAULT_RETRY_TIME = 5000;

    private boolean isShowing;
    private boolean portrait;
    private int volume = -1;
    private float brightness = -1;
    private long newPosition = -1;

    private int currentPosition;
    private boolean fullScreenOnly = false;

    private long mDuration;
    private boolean isSeeking;
    private boolean isScreenLock;

    private boolean isLive = false;//是否为直播

    /*********************************
     * 控件
     *********************************/
    private View viewRoot;
    private IjkVideoView mVideoView;
    private SeekBar mSeekBar;
    private ImageView videoPlay;
    private ImageView videoFullScreen;
    private ImageView videoReplay;
    private ImageView backIcon;

    private View volumeBox;
    private View brightnessBox;
    private View fastForwardBox;

    private ImageView volumeIcon;
    private TextView volumePercent;

    private ImageView brightnessIcon;
    private TextView brightnessPercent;

    private TextView fastForwardTime;
    private TextView fastForwardTarget;
    private TextView fastForwardAll;

    private View topBox;
    private TextView videoTitle;

    private View bottomBox;
    private ProgressBar loadingProgress;
    private View videoStatus;
    private TextView videoStatusText;
    private TextView videoCurrentTime;
    private TextView videoEndTime;

    private ImageView lock;

    /********************************************************/

    private static final int MESSAGE_SHOW_LOADING = 1;
    private static final int MESSAGE_HIDE_CONTROL = 2;
    private static final int MESSAGE_SEEK_NEW_POSITION = 3;
    private static final int MESSAGE_HIDE_CENTER_BOX = 4;
    private static final int MESSAGE_RESTART_PLAY = 5;

    @SuppressWarnings("HandlerLeak")
    private Handler mHandler = new Handler(Looper.getMainLooper()) {
        @Override
        public void handleMessage(Message msg) {
            switch (msg.what) {
                case MESSAGE_HIDE_CONTROL:
                    hideControl(false);
                    break;
                case MESSAGE_HIDE_CENTER_BOX:
                    volumeBox.setVisibility(View.GONE);
                    brightnessBox.setVisibility(View.GONE);
                    fastForwardBox.setVisibility(View.GONE);
                    break;
                case MESSAGE_SEEK_NEW_POSITION:
                    if (!isLive && newPosition >= 0) {
                        mVideoView.seekTo((int) newPosition);
                        newPosition = -1;
                    }
                    break;
                case MESSAGE_SHOW_LOADING:
                    setProgress();
                    if (!isSeeking && isShowing) {
                        msg = obtainMessage(MESSAGE_SHOW_LOADING);
                        sendMessageDelayed(msg, 1000);
                        updatePausePlay();
                    }
                    break;
                case MESSAGE_RESTART_PLAY:
                    play(mUrl);
                    break;
            }
        }
    };

    public WindyPlayer(final Activity activity) {
        try {
            IjkMediaPlayer.loadLibrariesOnce(null);
            IjkMediaPlayer.native_profileBegin("libijkplayer.so");
        } catch (Throwable e) {
            Log.e(TAG, "loadLibraries error", e);
        }
        mActivity = activity;
        initView(activity);
        screenWidthPixels = activity.getResources().getDisplayMetrics().widthPixels;
        // 初始高度
        initHeight = viewRoot.getLayoutParams().height;
        hideAll();

        mVideoView.setOnCompletionListener(onCompletionListener);
        mVideoView.setOnErrorListener(onErrorListener);
        mVideoView.setOnInfoListener(onInfoListener);

        mAudioManager = (AudioManager) activity.getSystemService(Context.AUDIO_SERVICE);
        mMaxVolume = mAudioManager.getStreamMaxVolume(AudioManager.STREAM_MUSIC);
        mGestureDetector = new GestureDetector(activity, new PlayerGestureListener());

        if (fullScreenOnly) {
            activity.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE);
        }
        portrait = (getScreenOrientation() == ActivityInfo.SCREEN_ORIENTATION_PORTRAIT);

        startOrientationEventListener();
        setScaleType(DEFAULT_SCALETYPE);
    }

    private void initView(final Activity activity) {
        mVideoView = (IjkVideoView) activity.findViewById(R.id.video_view);

        viewRoot = activity.findViewById(R.id.viewRoot);
        viewRoot.setClickable(true);
        viewRoot.setOnTouchListener(onTouchListener);

        videoReplay = (ImageView) activity.findViewById(R.id.app_video_replay_icon);
        videoReplay.setOnClickListener(onClickListener);

        loadingProgress = (ProgressBar) activity.findViewById(R.id.app_video_loading);
        videoStatus = activity.findViewById(R.id.app_video_status);
        videoStatusText = (TextView) activity.findViewById(R.id.app_video_status_text);

        volumeBox = activity.findViewById(R.id.app_video_volume_box);
        brightnessBox = activity.findViewById(R.id.app_video_brightness_box);
        fastForwardBox = activity.findViewById(R.id.app_video_fastForward_box);

        volumeIcon = (ImageView) activity.findViewById(R.id.app_video_volume_icon);
        volumePercent = (TextView) activity.findViewById(R.id.app_video_volume);
        brightnessIcon = (ImageView) activity.findViewById(R.id.app_video_brightness_icon);
        brightnessPercent = (TextView) activity.findViewById(R.id.app_video_brightness);
        fastForwardTime = (TextView) activity.findViewById(R.id.app_video_fastForward);
        fastForwardTarget = (TextView) activity.findViewById(R.id.app_video_fastForward_target);
        fastForwardAll = (TextView) activity.findViewById(R.id.app_video_fastForward_all);

        // top control bar
        topBox = activity.findViewById(R.id.topBox);
        backIcon = (ImageView) activity.findViewById(R.id.topLeftIcon);
        backIcon.setOnClickListener(onClickListener);
        videoTitle = (TextView) activity.findViewById(R.id.app_video_title);

        // bottom control bar
        bottomBox = activity.findViewById(R.id.bottomBox);
        videoCurrentTime = (TextView) activity.findViewById(R.id.app_video_currentTime);
        videoEndTime = (TextView) activity.findViewById(R.id.app_video_endTime);
        videoPlay = (ImageView) activity.findViewById(R.id.app_video_play);
        videoFullScreen = (ImageView) activity.findViewById(R.id.app_video_fullscreen);
        videoPlay.setOnClickListener(onClickListener);
        videoFullScreen.setOnClickListener(onClickListener);
        // seek bar
        mSeekBar = (SeekBar) activity.findViewById(R.id.app_video_seekBar);
        mSeekBar.setMax(1000);
        mSeekBar.setOnSeekBarChangeListener(mSeekListener);

        lock = (ImageView) activity.findViewById(R.id.lock);
        lock.setOnClickListener(onClickListener);
    }

    /**
     * set video title
     *
     * @param title
     */
    public void setTitle(CharSequence title) {
        videoTitle.setText(title);
    }

    /**
     * 隐藏返回图标(一般有actionbar or appToolbar时需要隐藏)
     */
    public void hideLeftIcon() {
        backIcon.setVisibility(View.GONE);
    }

    IMediaPlayer.OnCompletionListener onCompletionListener = new IMediaPlayer.OnCompletionListener() {
        @Override
        public void onCompletion(IMediaPlayer mp) {
            statusChange(STATUS_COMPLETED);
        }
    };

    IMediaPlayer.OnErrorListener onErrorListener = new IMediaPlayer.OnErrorListener() {
        @Override
        public boolean onError(IMediaPlayer mp, int what, int extra) {
            statusChange(STATUS_ERROR);
            return true;
        }
    };

    IMediaPlayer.OnInfoListener onInfoListener = new IMediaPlayer.OnInfoListener() {
        @Override
        public boolean onInfo(IMediaPlayer mp, int what, int extra) {
            switch (what) {
                case IMediaPlayer.MEDIA_INFO_BUFFERING_START:
                    statusChange(STATUS_LOADING);
                    break;
                case IMediaPlayer.MEDIA_INFO_BUFFERING_END:
                    statusChange(STATUS_PLAYING);
                    break;
                case IMediaPlayer.MEDIA_INFO_NETWORK_BANDWIDTH:
                    //显示 下载速度
                    Log.d(TAG, "download rate:" + extra);
                    break;
                case IMediaPlayer.MEDIA_INFO_VIDEO_RENDERING_START:
                    statusChange(STATUS_PLAYING);
                    break;
            }
            return false;
        }
    };

    private final View.OnClickListener onClickListener = new View.OnClickListener() {
        @Override
        public void onClick(View v) {
            int viewId = v.getId();
            if (viewId == R.id.topLeftIcon) {
                onBackPressed();
            } else if (viewId == R.id.app_video_fullscreen) {
                toggleScreenOrientation();
            } else if (viewId == R.id.app_video_play) {
                doPauseResume();
                showControl(DEFAULT_TIMEOUT);
            } else if (viewId == R.id.app_video_replay_icon) {
                if (!fullScreenOnly && !portrait) {
                    mActivity.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_PORTRAIT);
                } else {
                    mActivity.finish();
                }
            } else if (viewId == R.id.lock) {
                if (isScreenLock) {
                    unlockScreen();
                } else {
                    lockScreen();
                }
            }
        }
    };

    // 进度条滑动监听
    private final SeekBar.OnSeekBarChangeListener mSeekListener = new SeekBar.OnSeekBarChangeListener() {

        @Override
        public void onStartTrackingTouch(SeekBar seekBar) {
            isSeeking = true;
            showControl(MAX_TIMEOUT);
            mHandler.removeMessages(MESSAGE_SHOW_LOADING);
        }

        @Override
        public void onProgressChanged(SeekBar seekBar, int progress, boolean fromUser) {
            if (!fromUser) {
                return;
            }
            videoStatus.setVisibility(View.GONE);//移动时隐藏掉状态image
            int newPosition = (int) ((mDuration * progress * 1.0) / 1000);
            String time = StringUtil.generateTime(newPosition);
            videoCurrentTime.setText(time);
        }

        @Override
        public void onStopTrackingTouch(SeekBar seekBar) {
            mVideoView.seekTo((int) ((mDuration * seekBar.getProgress() * 1.0) / 1000));
            showControl(DEFAULT_TIMEOUT);
            isSeeking = false;
            mHandler.removeMessages(MESSAGE_SHOW_LOADING);
            mHandler.sendEmptyMessageDelayed(MESSAGE_SHOW_LOADING, 1000);
        }
    };

    // 手势监听
    public class PlayerGestureListener extends GestureDetector.SimpleOnGestureListener {

        private boolean firstTouch;
        private boolean volumeControl;
        private boolean toSeek;

        @Override
        public boolean onDoubleTap(MotionEvent e) {
            mVideoView.toggleAspectRatio();
            return true;
        }

        @Override
        public boolean onDown(MotionEvent e) {
            firstTouch = true;
            return super.onDown(e);
        }

        @Override
        public boolean onScroll(MotionEvent e1, MotionEvent e2, float distanceX, float distanceY) {
            if (isScreenLock) return true;

            float mOldX = e1.getX(), mOldY = e1.getY();
            float deltaY = mOldY - e2.getY();
            float deltaX = mOldX - e2.getX();
            if (firstTouch) {
                toSeek = Math.abs(distanceX) >= Math.abs(distanceY);
                volumeControl = mOldX > screenWidthPixels * 0.5f;
                firstTouch = false;
            }

            if (toSeek) {
                if (!isLive) {
                    onProgressSlide(-deltaX / mVideoView.getWidth());
                }
            } else {
                float percent = deltaY / mVideoView.getHeight();
                if (volumeControl) {
                    onVolumeSlide(percent);
                } else {
                    onBrightnessSlide(percent);
                }
            }
            return super.onScroll(e1, e2, distanceX, distanceY);
        }

        @Override
        public boolean onSingleTapUp(MotionEvent e) {
            if (isScreenLock) {
                if (lock.getVisibility() == View.VISIBLE) {
                    lock.setVisibility(View.GONE);
                } else {
                    lock.setVisibility(View.VISIBLE);
                }
                return true;
            }
            if (isShowing) {
                hideControl(false);
            } else {
                showControl(DEFAULT_TIMEOUT);
            }
            return true;
        }
    }

    private final View.OnTouchListener onTouchListener = new View.OnTouchListener() {
        @Override
        public boolean onTouch(View v, MotionEvent event) {
            if (mGestureDetector != null && mGestureDetector.onTouchEvent(event)) {
                return true;
            }
            // 处理手势结束
            switch (event.getAction() & MotionEvent.ACTION_MASK) {
                case MotionEvent.ACTION_UP:
                    endGesture();
                    break;
            }
            return false;
        }
    };

    /**
     * 手势结束
     */
    private void endGesture() {
        volume = -1;
        brightness = -1f;
        if (newPosition >= 0) {
            mHandler.removeMessages(MESSAGE_SEEK_NEW_POSITION);
            mHandler.sendEmptyMessage(MESSAGE_SEEK_NEW_POSITION);
        }
        mHandler.removeMessages(MESSAGE_HIDE_CENTER_BOX);
        mHandler.sendEmptyMessageDelayed(MESSAGE_HIDE_CENTER_BOX, 500);
    }


    /**
     * 滑动改变声音大小
     *
     * @param percent
     */
    private void onVolumeSlide(float percent) {
        if (volume == -1) {
            volume = mAudioManager.getStreamVolume(AudioManager.STREAM_MUSIC);
            if (volume < 0) {
                volume = 0;
            }
        }
        int index = (int) (percent * mMaxVolume) + volume;
        if (index > mMaxVolume) {
            index = mMaxVolume;
        } else if (index < 0) {
            index = 0;
        }
        // 变更声音
        mAudioManager.setStreamVolume(AudioManager.STREAM_MUSIC, index, 0);
        // 变更进度条
        int i = (int) (index * 1.0 / mMaxVolume * 100);
        String s = i + "%";
        if (i == 0) {
            s = "off";
        }
        volumeBox.setVisibility(View.VISIBLE);
        volumeIcon.setImageResource(i == 0 ? R.drawable.ic_volume_off_white_36dp : R.drawable.ic_volume_up_white_36dp);
        volumePercent.setText(s);
    }

    /**
     * 滑动改变进度
     *
     * @param percent
     */
    private void onProgressSlide(float percent) {
        long position = mVideoView.getCurrentPosition();
        long duration = mVideoView.getDuration();
        long deltaMax = Math.min(100 * 1000, duration - position);
        long delta = (long) (deltaMax * percent);

        newPosition = delta + position;
        if (newPosition > duration) {
            newPosition = duration;
        } else if (newPosition <= 0) {
            newPosition = 0;
            delta = -position;
        }
        int showDelta = (int) delta / 1000;
        if (showDelta != 0) {
            fastForwardBox.setVisibility(View.VISIBLE);
            String text = showDelta > 0 ? ("+" + showDelta) : "" + showDelta;
            fastForwardTime.setText(text + "s");
            fastForwardTarget.setText(StringUtil.generateTime(newPosition) + "/");
            fastForwardAll.setText(StringUtil.generateTime(duration));
        }
    }

    /**
     * 滑动改变亮度
     *
     * @param percent
     */
    private void onBrightnessSlide(float percent) {
        if (brightness < 0) {
            brightness = mActivity.getWindow().getAttributes().screenBrightness;
            if (brightness <= 0.00f) {
                brightness = 0.50f;
            } else if (brightness < 0.01f) {
                brightness = 0.01f;
            }
        }
        Log.d(TAG, "brightness:" + brightness + ",percent:" + percent);
        brightnessBox.setVisibility(View.VISIBLE);
        WindowManager.LayoutParams lpa = mActivity.getWindow().getAttributes();
        lpa.screenBrightness = brightness + percent;
        if (lpa.screenBrightness > 1.0f) {
            lpa.screenBrightness = 1.0f;
        } else if (lpa.screenBrightness < 0.01f) {
            lpa.screenBrightness = 0.01f;
        }
        brightnessPercent.setText(((int) (lpa.screenBrightness * 100)) + "%");
        mActivity.getWindow().setAttributes(lpa);
    }

    /**
     * 初始化OrientationEventListener
     */
    private void startOrientationEventListener() {
        mOrientationEventListener = new OrientationEventListener(mActivity) {
            @Override
            public void onOrientationChanged(int orientation) {
                Log.d("dingfeng", "onOrientationChanged:" + orientation);

                if ((orientation >= 0 && orientation <= 30) || orientation >= 330 || (orientation >= 150 && orientation <= 210)) {
                    //竖屏
                    if (portrait) {
                        mActivity.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_SENSOR);
                        mOrientationEventListener.disable();
                    }
                } else if ((orientation >= 90 && orientation <= 120) || (orientation >= 240 && orientation <= 300)) {
                    if (!portrait) {
                        mActivity.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_SENSOR);
                        mOrientationEventListener.disable();
                    }
                }
            }
        };
    }

    /**
     * 启用屏幕方向监听
     */
    private void enableOrientationEvent() {
        if (mOrientationEventListener != null) {
            mOrientationEventListener.enable();
        }
    }

    /**
     * 禁用屏幕方向监听
     */
    private void disableOrientationEvent() {
        if (mOrientationEventListener != null) {
            mOrientationEventListener.disable();
        }
    }

    /**
     * try to play when error(only for live video)
     *
     * @param defaultRetryTime millisecond,0 will stop retry,default is 5000 millisecond
     */
    public void setDefaultRetryTime(long defaultRetryTime) {
        DEFAULT_RETRY_TIME = defaultRetryTime;
    }

    private void doPauseResume() {
        if (status == STATUS_COMPLETED) {
            videoReplay.setVisibility(View.GONE);
            mVideoView.seekTo(0);
            mVideoView.start();
        } else if (mVideoView.isPlaying()) {
            statusChange(STATUS_PAUSE);
            mVideoView.pause();
        } else {
            mVideoView.start();
        }
        updatePausePlay();
    }

    private void updatePausePlay() {
        if (mVideoView.isPlaying()) {
            videoPlay.setImageResource(R.drawable.ic_stop_white_24dp);
        } else {
            videoPlay.setImageResource(R.drawable.ic_play_arrow_white_24dp);
        }
    }

    /**
     * 隐藏所有控件
     */
    private void hideAll() {
        videoReplay.setVisibility(View.GONE);
        loadingProgress.setVisibility(View.GONE);
        videoStatus.setVisibility(View.GONE);
        hideControl(true);
    }

    /**
     * 视频状态变化
     *
     * @param newStatus
     */
    private void statusChange(int newStatus) {
        status = newStatus;
        if (!isLive && newStatus == STATUS_COMPLETED) {
            mHandler.removeMessages(MESSAGE_SHOW_LOADING);
            hideAll();
            videoReplay.setVisibility(View.VISIBLE);
        } else if (newStatus == STATUS_ERROR) {
            mHandler.removeMessages(MESSAGE_SHOW_LOADING);
            hideAll();
            if (isLive) {
                showStatus(mActivity.getResources().getString(R.string.small_problem));
                if (DEFAULT_RETRY_TIME > 0) {
                    mHandler.sendEmptyMessageDelayed(MESSAGE_RESTART_PLAY, DEFAULT_RETRY_TIME);
                }
            } else {
                showStatus(mActivity.getResources().getString(R.string.small_problem));
            }
        } else if (newStatus == STATUS_LOADING) {
            hideAll();
            loadingProgress.setVisibility(View.VISIBLE);
        } else if (newStatus == STATUS_PLAYING) {
            hideAll();
        }
    }

    /**
     * 显示状态
     *
     * @param statusText
     */
    private void showStatus(String statusText) {
        videoStatus.setVisibility(View.VISIBLE);
        videoStatusText.setText(statusText);
    }

    /**
     * 锁住屏幕，禁止返回操作
     */
    private void lockScreen() {
        isScreenLock = true;
        lock.setImageResource(R.drawable.player_control_lock);
        hideControl(true);

        int orientation = getScreenOrientation();
        if (orientation == ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE) {
            mActivity.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE);
        } else if (orientation == ActivityInfo.SCREEN_ORIENTATION_REVERSE_LANDSCAPE) {
            mActivity.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_REVERSE_LANDSCAPE);
        } else {
            mActivity.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_PORTRAIT);
        }
        disableOrientationEvent();

    }

    private void unlockScreen() {
        isScreenLock = false;
        lock.setImageResource(R.drawable.player_control_unlock);
        showControl(DEFAULT_TIMEOUT);

        enableOrientationEvent();
    }

    /**
     * Activity onResume 时调用
     */
    public void onResume() {
        if (status == STATUS_PLAYING) {
            if (isLive) {
                mVideoView.seekTo(0);
            } else {
                if (currentPosition > 0) {
                    mVideoView.seekTo(currentPosition);
                }
            }
            mVideoView.start();
        }
    }

    /**
     * Activity onPause 时调用
     */
    public void onPause() {
        showControl(0);
        if (status == STATUS_PLAYING) {
            mVideoView.pause();
            if (!isLive) {
                currentPosition = mVideoView.getCurrentPosition();
            }
        }
    }

    /**
     * Activity onDestroy 时调用
     */
    public void onDestroy() {
        mHandler.removeCallbacksAndMessages(null);
        mVideoView.stopPlayback();
        disableOrientationEvent();
    }

    /**
     * 屏幕方向变化
     *
     * @param newConfig
     */
    public void onConfigurationChanged(final Configuration newConfig) {
        portrait = (newConfig.orientation == Configuration.ORIENTATION_PORTRAIT);
        doOnConfigurationChanged(portrait);
    }

    /**
     * 处理屏幕方向变化
     *
     * @param portrait
     */
    private void doOnConfigurationChanged(final boolean portrait) {
        if (mVideoView != null && !fullScreenOnly) {
            mHandler.post(new Runnable() {
                @Override
                public void run() {
                    tryFullScreen(!portrait);
                    ViewGroup.LayoutParams lp = viewRoot.getLayoutParams();
                    if (portrait) {
                        lp.height = initHeight;
                        viewRoot.setLayoutParams(lp);
                    } else {
                        int heightPixels = mActivity.getResources().getDisplayMetrics().heightPixels;
                        int widthPixels = mActivity.getResources().getDisplayMetrics().widthPixels;
                        lp.height = Math.min(heightPixels, widthPixels);
                        viewRoot.setLayoutParams(lp);
                    }
                    toggleFullScreenButton();
                    showLockButton(!portrait);
                }
            });

            enableOrientationEvent();
        }
    }

    /**
     * 全屏时将actionbar隐藏
     *
     * @param fullScreen
     */
    private void tryFullScreen(boolean fullScreen) {
        if (mActivity instanceof AppCompatActivity) {
            ActionBar supportActionBar = ((AppCompatActivity) mActivity).getSupportActionBar();
            if (supportActionBar != null) {
                if (fullScreen) {
                    supportActionBar.hide();
                } else {
                    supportActionBar.show();
                }
            }
        }
        setFullScreen(fullScreen);
        showFullScreenButton(!fullScreenOnly);
        showLockButton(!fullScreenOnly);
    }

    /**
     * 设为全屏
     *
     * @param fullScreen
     */
    private void setFullScreen(boolean fullScreen) {
        if (mActivity != null) {
            WindowManager.LayoutParams attrs = mActivity.getWindow().getAttributes();
            if (fullScreen) {
                attrs.flags |= WindowManager.LayoutParams.FLAG_FULLSCREEN;
                mActivity.getWindow().setAttributes(attrs);
                mActivity.getWindow().addFlags(WindowManager.LayoutParams.FLAG_LAYOUT_NO_LIMITS);
            } else {
                attrs.flags &= (~WindowManager.LayoutParams.FLAG_FULLSCREEN);
                mActivity.getWindow().setAttributes(attrs);
                mActivity.getWindow().clearFlags(WindowManager.LayoutParams.FLAG_LAYOUT_NO_LIMITS);
            }
        }
    }

    /**
     * 切换屏幕方向
     */
    public void toggleScreenOrientation() {
        if (getScreenOrientation() == ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE) {
            mActivity.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_PORTRAIT);
        } else {
            mActivity.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE);
        }
        toggleFullScreenButton();
    }

    /**
     * 屏幕方向
     *
     * @return
     */
    private int getScreenOrientation() {
        int rotation = mActivity.getWindowManager().getDefaultDisplay().getRotation();
        DisplayMetrics dm = new DisplayMetrics();
        mActivity.getWindowManager().getDefaultDisplay().getMetrics(dm);
        int width = dm.widthPixels;
        int height = dm.heightPixels;
        int orientation;
        // if the device's natural orientation is portrait:
        if ((rotation == Surface.ROTATION_0
                || rotation == Surface.ROTATION_180) && height > width ||
                (rotation == Surface.ROTATION_90
                        || rotation == Surface.ROTATION_270) && width > height) {
            switch (rotation) {
                case Surface.ROTATION_0:
                    orientation = ActivityInfo.SCREEN_ORIENTATION_PORTRAIT;
                    break;
                case Surface.ROTATION_90:
                    orientation = ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE;
                    break;
                case Surface.ROTATION_180:
                    orientation = ActivityInfo.SCREEN_ORIENTATION_REVERSE_PORTRAIT;
                    break;
                case Surface.ROTATION_270:
                    orientation = ActivityInfo.SCREEN_ORIENTATION_REVERSE_LANDSCAPE;
                    break;
                default:
                    orientation = ActivityInfo.SCREEN_ORIENTATION_PORTRAIT;
                    break;
            }
        }
        // if the device's natural orientation is landscape or if the device
        // is square:
        else {
            switch (rotation) {
                case Surface.ROTATION_0:
                    orientation = ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE;
                    break;
                case Surface.ROTATION_90:
                    orientation = ActivityInfo.SCREEN_ORIENTATION_PORTRAIT;
                    break;
                case Surface.ROTATION_180:
                    orientation = ActivityInfo.SCREEN_ORIENTATION_REVERSE_LANDSCAPE;
                    break;
                case Surface.ROTATION_270:
                    orientation = ActivityInfo.SCREEN_ORIENTATION_REVERSE_PORTRAIT;
                    break;
                default:
                    orientation = ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE;
                    break;
            }
        }
        return orientation;
    }

    /**
     * set seek bar progress
     *
     * @return
     */
    private long setProgress() {
        if (isSeeking) {
            return 0;
        }
        long position = mVideoView.getCurrentPosition();
        long duration = mVideoView.getDuration();
        if (mSeekBar != null) {
            if (duration > 0) {
                long pos = 1000L * position / duration;
                mSeekBar.setProgress((int) pos);
            }
            int percent = mVideoView.getBufferPercentage();
            mSeekBar.setSecondaryProgress(percent * 10);
        }
        mDuration = duration;
        videoCurrentTime.setText(StringUtil.generateTime(position));
        videoEndTime.setText(StringUtil.generateTime(mDuration));
        return position;
    }

    /**
     * 显示控制栏
     *
     * @param timeout
     */
    public void showControl(int timeout) {
        if (!isShowing) {
            topBox.setVisibility(View.VISIBLE);
            bottomBox.setVisibility(View.VISIBLE);
            // animation
            int topHeight = topBox.getHeight();
            int bottomHeight = bottomBox.getHeight();
            AnimatorSet animatorSet = new AnimatorSet();
            ObjectAnimator topDriftY = ObjectAnimator.ofFloat(topBox, "translationY", -topHeight, 0.0f);
            ObjectAnimator bottomDriftY = ObjectAnimator.ofFloat(bottomBox, "translationY", bottomHeight, 0.0f);

            animatorSet.playTogether(topDriftY, bottomDriftY);
            animatorSet.setDuration(300);
            animatorSet.setInterpolator(new DecelerateInterpolator());
            animatorSet.start();

            showLockButton(!portrait);

            isShowing = true;
        }
        updatePausePlay();
        mHandler.sendEmptyMessage(MESSAGE_SHOW_LOADING);
        mHandler.removeMessages(MESSAGE_HIDE_CONTROL);
        if (timeout != 0) {
            mHandler.sendMessageDelayed(mHandler.obtainMessage(MESSAGE_HIDE_CONTROL), timeout);
        }
    }

    /**
     * 隐藏控制栏
     *
     * @param force
     */
    public void hideControl(boolean force) {
        if (force || isShowing) {
            mHandler.removeMessages(MESSAGE_SHOW_LOADING);

            int topHeight = topBox.getHeight();
            int bottomHeight = bottomBox.getHeight();
            AnimatorSet animatorSet = new AnimatorSet();
            ObjectAnimator topDriftY = ObjectAnimator.ofFloat(topBox, "translationY", 0.0f, -topHeight);
            ObjectAnimator bottomDriftY = ObjectAnimator.ofFloat(bottomBox, "translationY", 0.0f, bottomHeight);
            animatorSet.playTogether(topDriftY, bottomDriftY);
            animatorSet.setDuration(300);
            animatorSet.setInterpolator(new DecelerateInterpolator());
            animatorSet.start();
            animatorSet.addListener(new AnimatorListenerAdapter() {
                @Override
                public void onAnimationEnd(Animator animation) {
                    super.onAnimationEnd(animation);
                    topBox.setVisibility(View.INVISIBLE);
                    bottomBox.setVisibility(View.INVISIBLE);
                    showLockButton(false);
                    isShowing = false;
                }
            });
        }
    }

    /**
     * 播放
     *
     * @param url
     */
    public void play(String url) {
        mUrl = url;
        loadingProgress.setVisibility(View.VISIBLE);
        mVideoView.setVideoPath(url);
        start();
    }

    /**
     * 开始播放
     */
    public void start() {
        mVideoView.start();
    }

    /**
     * 暂停播放
     */
    public void pause() {
        mVideoView.pause();
    }

    /**
     * 是否正在播放
     *
     * @return
     */
    public boolean isPlaying() {
        return mVideoView != null ? mVideoView.isPlaying() : false;
    }

    /**
     * 停止播放
     */
    public void stop() {
        mVideoView.stopPlayback();
    }

    /**
     * seekTo position
     *
     * @param sec millisecond
     */
    public void seekTo(int sec) {
        mVideoView.seekTo(sec);
    }

    /**
     * get video duration
     *
     * @return
     */
    public int getDuration() {
        return mVideoView.getDuration();
    }

    /**
     * 向前滑动
     *
     * @param percent
     */
    public void forward(float percent) {
        if (isLive || percent > 1 || percent < -1) {
            return;
        }
        onProgressSlide(percent);
        mHandler.sendEmptyMessage(MESSAGE_SHOW_LOADING);
        endGesture();
    }

    /**
     * 当前播放进度
     *
     * @return
     */
    public int getCurrentPosition() {
        return mVideoView.getCurrentPosition();
    }

    /**
     * 切换全屏按钮样式
     */
    private void toggleFullScreenButton() {
        if (getScreenOrientation() == ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE) {
            videoFullScreen.setImageResource(R.drawable.ic_fullscreen_exit_white_36dp);
        } else {
            videoFullScreen.setImageResource(R.drawable.ic_fullscreen_white_24dp);
        }
    }

    /**
     * 是否隐藏全屏按钮
     *
     * @param show
     */
    private void showFullScreenButton(boolean show) {
        if (show) {
            videoFullScreen.setVisibility(View.VISIBLE);
        } else {
            videoFullScreen.setVisibility(View.INVISIBLE);
        }
    }

    /**
     * 是否隐藏锁屏按钮
     *
     * @param show
     */
    private void showLockButton(boolean show) {
        if (show) {
            lock.setVisibility(View.VISIBLE);
        } else {
            lock.setVisibility(View.INVISIBLE);
        }
    }

    /**
     * 只全屏播放
     *
     * @param fullScreenOnly
     */
    public void setFullScreenOnly(boolean fullScreenOnly) {
        this.fullScreenOnly = fullScreenOnly;
        tryFullScreen(fullScreenOnly);
        if (fullScreenOnly) {
            ViewGroup.LayoutParams lp = viewRoot.getLayoutParams();
            int heightPixels = mActivity.getResources().getDisplayMetrics().heightPixels;
            int widthPixels = mActivity.getResources().getDisplayMetrics().widthPixels;
            lp.height = Math.min(heightPixels, widthPixels);
            viewRoot.setLayoutParams(lp);
        }

        if (fullScreenOnly) {
            mActivity.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE);
        } else {
            mActivity.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_SENSOR);
        }

    }

    /**
     * 全屏播放
     *
     * @param fullScreen
     */
    public void playInFullScreen(boolean fullScreen) {
        if (fullScreen) {
            mActivity.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE);
            toggleFullScreenButton();
        }
    }

    /**
     * using constants in GiraffePlayer,eg: GiraffePlayer.SCALETYPE_FITPARENT
     *
     * @param scaleType
     */
    public void setScaleType(String scaleType) {
        if (SCALETYPE_FITPARENT.equals(scaleType)) {
            mVideoView.setAspectRatio(IRenderView.AR_ASPECT_FIT_PARENT);
        } else if (SCALETYPE_FILLPARENT.equals(scaleType)) {
            mVideoView.setAspectRatio(IRenderView.AR_ASPECT_FILL_PARENT);
        } else if (SCALETYPE_WRAPCONTENT.equals(scaleType)) {
            mVideoView.setAspectRatio(IRenderView.AR_ASPECT_WRAP_CONTENT);
        } else if (SCALETYPE_FITXY.equals(scaleType)) {
            mVideoView.setAspectRatio(IRenderView.AR_MATCH_PARENT);
        } else if (SCALETYPE_16_9.equals(scaleType)) {
            mVideoView.setAspectRatio(IRenderView.AR_16_9_FIT_PARENT);
        } else if (SCALETYPE_4_3.equals(scaleType)) {
            mVideoView.setAspectRatio(IRenderView.AR_4_3_FIT_PARENT);
        }
    }

    /**
     * 切换宽高比
     */
    public void toggleAspectRatio() {
        if (mVideoView != null) {
            mVideoView.toggleAspectRatio();
        }
    }

    /**
     * set is live (can't seek forward)
     *
     * @param isLive
     * @return
     */
    public void live(boolean isLive) {
        this.isLive = isLive;
    }

    public void onBackPressed() {
        if (isScreenLock) return;
        if (!fullScreenOnly && !portrait) {
            mActivity.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_PORTRAIT);
            return;
        }
        onDestroy();
        mActivity.finish();
    }

}
